package com.earth.c.handler;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.shiro.authc.AuthenticationException;
import org.apache.shiro.authz.UnauthenticatedException;
import org.springframework.boot.web.servlet.error.ErrorController;
import org.springframework.validation.BindException;
import org.springframework.web.HttpRequestMethodNotSupportedException;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.servlet.ModelAndView;
import com.earth.c.render.Result;
import com.jfinal.kit.StrKit;

@ControllerAdvice
public class GlobalExceptionHandler implements ErrorController {

	@ExceptionHandler(Exception.class)
	public ModelAndView handleException(Throwable e,HttpServletRequest request, HttpServletResponse response) {
		ModelAndView modelAndView ;
		if (!StrKit.isBlank(request.getHeader("x-requested-with"))
				&& request.getHeader("x-requested-with").equals("XMLHttpRequest")) {
			modelAndView = new ModelAndView("redirect:/error/backJson");
		} else {
			modelAndView = new ModelAndView("redirect:/error/backHtml");
		}
		
		if (e instanceof AuthenticationException) {
			modelAndView.addObject("code", 500);
			modelAndView.addObject("error", "该用户不存在或密码错误!");
		} else if (e instanceof UnauthenticatedException) {
			modelAndView.addObject("code", 401);
			modelAndView.addObject("error", "登录过期!");
		} else if (e instanceof BindException) {
			modelAndView.addObject("code", 400);
			modelAndView.addObject("error", "参数有误!");
		} else if (e instanceof HttpRequestMethodNotSupportedException) {
			modelAndView.addObject("code", 405);
			modelAndView.addObject("error", "不允许的方法!");
		} else {
			modelAndView.addObject("code", 500);
			modelAndView.addObject("error", e.getMessage());
		}
		return modelAndView;
	}

	@GetMapping(value = "/error/backJson")
	@ResponseBody
	public Result backJson( int code, String error) {
		return new Result(code, error);
	}

	@GetMapping(value = "/error/backHtml")
	public String backHtml(int code, String error) {
		if (401 == code) {
			return "redirect:/login";
		} else {
			return "redirect:/error.html";
		}
	}
}
